<html>
<head>
  <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
  <title>The Qur'an</title>
<style type="text/css">
html { font-family: Georgia, Verdana; }
h1 {
  margin: 0px;
  padding: 5px;
  font-family: Arial;
  font-size: 1.2em;
  background-color: #CCDDEE;
  border-bottom: 2px solid #399;
}
h1 a { text-decoration: none; color: #237;}
h1 a:hover { color: #469; }
h1 span { font-size: 0.5em; }
h2 { cursor: pointer; }
h2:hover { color: #309; }
.hidden { display: none }
#authorList p { margin: 0 0 0 10px; padding: 0px; }
h2 { margin-left: 5px; font-size: 1em; }
.cellborder { border: 1px solid #CCE; }
a { color: #339; text-decoration: none; }
#helplnk {
  position:absolute;
  right:0px;
  top:0px;
  padding:5px;
  margin:0px;
}
#help h2:hover { color: black; }
#help div { margin: 0 1em; }
#text {
  margin: auto 10%;
}
/* Highlighted matches */
#text em {
  font-style: normal;
  background-color: #FF6;
  border-bottom: 1px solid #DD5;
}
#error em {
  font-style: normal;
  background-color: #F55;
}
#refs { width: 250px; }
#search { width: 250px; }
.foundM span { cursor: pointer; }
/* Verse */
.v { margin: 5px 30px;}
/* Reference */
.r {
  font-family: Arial;
  margin: 0 15px;
  font-weight: bold;
  font-size: 0.7em;
}
/* Author name normal */
.author {
  font-weight: bold;
  color: #692213;
}
/* Author name small */
.as {
  color: #777;
  margin: 0 15px;
  font-size: 0.8em;
}
.basmalah {
  font-style: italic;
  margin: 10px 15px;
}
/* Language styles */
.l_ar {
  font-family: "Traditional Arabic";
  direction: rtl;
}
.l_ar p.v, .l_ar h2, h2.l_ar, .l_ar .author {
  font-size: 1.6em;
}
.l_ar .basmalah, .l_ar .as { font-size: 1.3em; }
</style>
<script type="text/javascript">
{%Quran.js%}
</script>
<script type="text/javascript">
{%Query.js%}
</script>
<script type="text/javascript">
{%ReferenceParser.js%}
</script>
<script type="text/javascript">
var g_Authors = {%QuranObjects%}
/**
  Author: Aziz Köksal
  License: GPL2
*/
/**
  History class for keeping track of commands typed in a text box.
*/
function History()
{
  this.current = 0;
  this.array = [];
  this.getCurrent = function()
  {
    if (this.current == this.array.length)
      return "";
    return this.array[this.current];
  }
  this.add = function(item)
  {
    // Don't add item if the current item is the special, empty string
    // OR if it matches the last item in the array.
    if ((this.current == this.array.length || this.current == this.array.length -1) &&
         this.getCurrent() == item)
      return;

    this.array.push( item );
    this.current = this.array.length -1;
  }
  this.prev = function()
  {
    if (this.current > 0)
      this.current--;
    return this.getCurrent();
  }
  this.next = function()
  {
    if (this.current <= this.array.length - 1)
      this.current++;
    return this.getCurrent();
  }
}

function debug(msg)
{
  document.getElementById('debug').appendChild(document.createTextNode(msg+"\n"));
}

function onHeaderClick(header)
{
  var divTag = header.nextSibling;
  if (divTag.className == "")
    divTag.className = "hidden";
  else
    divTag.className = "";
}

function getActiveAuthors()
{
  var list = document.getElementById("authorList");
  var authors = list.getElementsByTagName("input");
  var active = [];
  for(var i=0; i < authors.length; ++i)
  {
    var cbox = authors[i];
    if (cbox.checked)
      active.push(g_Authors[cbox.authorIdx]);
  }
  return active;
}

function showBBCode()
{
  var text = document.getElementById("text");
  var props = text.textProperties;
  var divBBC = text.firstChild; //document.getElementById("BBCode");

  var code = "";
  // Start with node past divBBC.
  var node = divBBC.nextSibling;
  function genCode()
  {
    var skipFound = props.type == "search" ? true : false;
    do
    {
      if (skipFound)
        node = node.nextSibling; // Skip "Found..."
      code += "[b]" + getText(node.firstChild) + "[/b]\n";
      var div = node;
      node = div.firstChild.nextSibling.firstChild;
      do
      {
        code += "[size=18]" + getText(node) + "[/size]\n";
        var div2 = node.nextSibling;
        // traverse children of div-tag
        node = div2.firstChild;
        if (node.className != "r")
        {
          code += "[i]" + getText(node) + "[/i]\n";
          node = node.nextSibling;
        }
        do
        {
          code += "[size=13]" + getText(node) + "[/size]\n";
          node = node.nextSibling;
          code += getText(node) + "\n";
        } while (node = node.nextSibling);
        node = div2.nextSibling; // leave div-tag
      } while (node);
      node = div.nextSibling;
    } while (node);
  }

  if (props.type == "show" && props.interleaved)
  {
    do
    {
      code += "[size=18]" + getText(node) + "[/size]\n";
      var div = node.nextSibling;
      // traverse children of div-tag
      node = div.firstChild;
      if (node.className.slice(0,1) != "r")
      {
        code += "[i]" + getText(node) + "[/i]\n";
        node = node.nextSibling;
      }
      do
      {
        code += "[size=13]" + getText(node) + "[/size]\n";
        node = node.nextSibling;
        do
        {
          code += "[size=13]" + getText(node.firstChild) + ":[/size]\n";
          code += getText(node.lastChild) + "\n";
          node = node.nextSibling
        } while (node && node.tagName == "DIV");
      } while (node);
      node = div; // leave div-tag
    } while (node = node.nextSibling);
  }
  else
  {
    genCode();
  }

  divBBC.innerHTML = '<a href="javascript:hideBBCode()">Hide BBCode</a><br>';

  var textarea = divBBC.appendChild(document.createElement("textarea"));
  textarea.rows = 20;
  textarea.cols = 40;
  textarea.value = code;
}

function hideBBCode()
{
  var div = document.getElementById("BBCode")
  div.innerHTML = '<a href="javascript:showBBCode()">Show BBCode</a>';
}

function setText(html, textProperties)
{
  var text = document.getElementById("text");
  text.innerHTML = html;
  text.textProperties = textProperties;

  var p = text.insertBefore(document.createElement("p"), text.firstChild);
  p.id = "BBCode";
  hideBBCode();

  // Show chapters expanded if html is not too long.
  if (html.length < 100000)
  {
    var divs = text.getElementsByTagName("div");
    for(var i=0; i < divs.length; ++i)
    {
      if (divs[i].className == "hidden")
        divs[i].className = "";
    }
  }
}

function show(refsStr)
{
  var authors = getActiveAuthors();
  var refs = parseReferencesHE(refsStr);
  if (authors.length == 0 || refs.length == 0)
    return;

  var html = "";

  var interleave = document.getElementById("interleave");

  if (interleave.checked && authors.length > 1)
  {
    // We take the chapter titles and basmalah from the first author
    // in the array
    var author = authors[0];
    var langClass = author.langClass;
    for(var i=0; i < refs.length; ++i)
    {
      var aref = refs[i];
      var cindices = aref.getChapterIndices();
      for(var j=0; j < cindices.length; ++j)
      {
        var cidx = cindices[j];
        var cidxStr = ""+(cidx+1);
        var vindices = aref.getVerseIndices(cidx);
        html += '<h2 class="'+langClass+'" onclick="onHeaderClick(this)">'+cidxStr+". "+author.titles[cidx]+'</h2><div class="hidden">';
        if (cidx != 0 && cidx != 8) // Don't add Basmalah for chapter 1 and 9
          html += '<p class="basmalah '+langClass+'">'+author.verses[0]+"</p>";
        for(var k=0; k < vindices.length; ++k)
        {
          var vidx = vindices[k];
          html += '<p class="r '+langClass+'">'+cidxStr+":"+(vidx+1)+"</p>";
          for(var l=0; l < authors.length; ++l)
          {
            var a = authors[l];
            html += '<div class="'+a.langClass+'"><p class="as">'+a.name+'</p><p class="v">'+ a.chapters[cidx][vidx] + "</p></div>";
          }
        }
        html += "</div>";
      }
    }
  }
  else
  {
    for(var i=0; i < authors.length; ++i)
    {
      var author = authors[i];
      html += '<div class="'+author.langClass+'"><p class="author">'+author.name+':</p><div>';
      for(var j=0; j < refs.length; ++j)
      {
        var aref = refs[j];
        var cindices = aref.getChapterIndices();
        for(var k=0; k < cindices.length; ++k)
        {
          var cidx = cindices[k];
          var cidxStr = ""+(cidx+1);
          var chapter = author.chapters[cidx];
          var vindices = aref.getVerseIndices(cidx);
          html += "<h2 onclick='onHeaderClick(this)'>"+cidxStr+". "+author.titles[cidx]+'</h2><div class="hidden">';
          if (cidx != 0 && cidx != 8) // Don't add Basmalah for chapter 1 and 9
            html += '<p class="basmalah">'+author.verses[0]+"</p>";
          for(var l=0; l < vindices.length; ++l)
          {
            var vidx = vindices[l];
            html += '<p class="r">'+cidxStr+":"+(vidx+1)+"</p>";
            html += '<p class="v">'+ chapter[vidx] + "</p>";
          }
          html += "</div>";
        }
      }
      html += "</div></div>";
    }
  }

  setText(html, {type:"show", interleaved: interleave.checked});
}

function showFoundRefs(span, index)
{
  var text = document.getElementById("text");
  span.parentNode.appendChild(document.createTextNode(text.textProperties.foundReferences[index].toString()));
//   span.setAttribute("onclick", "hideFoundRefs(this,"+index+")");
  span.foundRefsIdx = index;
  span.onclick = function(){hideFoundRefs(this,this.foundRefsIdx);};
  span.linkText = span.firstChild.data;
  span.firstChild.data = "Hide found references.";
}

function hideFoundRefs(span, index)
{
  span.parentNode.innerHTML = '<span onclick="showFoundRefs(this,'+index+')">'+span.linkText+"</span><br/>";
}

function FoundRefs()
{
  this.array = new Array(NR_OF_CHAPTERS);
  for (var i=0; i < NR_OF_CHAPTERS; ++i)
    this.array[i] = [];
  this.push = function(cidx, vidx)
  {
    var a = this.array;
    if (a[cidx].length)
    {
      var r = a[cidx][a[cidx].length-1];
      var cmp = r[1];
      if (!cmp)
        cmp = r[0];
      if (cmp+1 == vidx)
      {
        r[1] = vidx;
        return;
      }
      // else push new range below
    }

    a[cidx].push( [vidx, 0] );
  }
  this.toString = function()
  {
    var str = "";
    for (var i=0; i < NR_OF_CHAPTERS; ++i)
    {
      var a = this.array[i];
      if (a.length)
      {
        if (a.length == 1 && a[0][0] == 1 && a[0][1] == verses_table[i])
        {
          str += i+1+"; ";
          continue;
        }

        str += i+1+":";
        for (var j=0; j < a.length; ++j)
        {
          var l = a[j][0], r = a[j][1];
          if (r)
            str += l+"-"+r+",";
          else
            str += l+",";
        }
        str = str.slice(0, str.length-1) + "; ";
      }
    }
    return str;
  }
}

function search(query)
{
  var hl = document.getElementById("highlight").checked;
  var matchany = document.getElementById("matchany").checked;
  var casei = document.getElementById("casei").checked;
  var search = parseQueryHE(query, matchany, hl, casei);
  if (!search)
    return;

  var authors = getActiveAuthors();
  if (authors.length == 0)
    return;

  var refsString;
  if (document.getElementById("restrict").checked)
    refsString = document.getElementById("refs").value;
  else
    refsString = "1-114"; // Search all chapters

  var refs = parseReferencesHE(refsString);
  if (refs.length == 0)
    return;

  var foundRefs = new Array(authors.length);

  var html = "";
  for(var i=0; i < authors.length; ++i)
  {
    var author = authors[i];
    var totalNrOfMatches = 0;
    foundRefs[i] = new FoundRefs();
    var htmlauthor = "";
    for(var j=0; j < refs.length; ++j)
    {
      var aref = refs[j];
      var cindices = aref.getChapterIndices();
      for(var k=0; k < cindices.length; ++k)
      {
        var cidx = cindices[k];
        var cidxStr = ""+(cidx+1);
        var chapter = author.chapters[cidx];
        var vindices = aref.getVerseIndices(cidx);
        var htmlfound = "";
        for(var l=0; l < vindices.length; ++l)
        {
          var vidx = vindices[l];
          if (search.doSearch(chapter[vidx]))
          {
            htmlfound += '<p class="r">'+cidxStr+":"+(vidx+1)+"</p>" +
                         '<p class="v">'+ search.highlight(chapter[vidx]) + "</p>";
            ++totalNrOfMatches;
            foundRefs[i].push(cidx, vidx+1);
          }
        }
        if (htmlfound.length)
        {
          htmlauthor += "<h2 onclick='onHeaderClick(this)'>"+cidxStr+". "+author.titles[cidx]+'</h2><div class="hidden">' +
                        htmlfound + "</div>";
        }
      }
    }
    html += '<p class="foundM"><span'+
            (totalNrOfMatches?' onclick="showFoundRefs(this,'+i+');return false;"':'')+
            '>Found '+totalNrOfMatches+" match"+(totalNrOfMatches==1?"":"es")+
            ':</span><br/></p><div class="'+author.langClass+
            '"><p class="author">'+author.name+':</p><div>' + htmlauthor + "</div></div>";
  }

  setText(html, {type:"search", highlighted: hl, foundReferences : foundRefs});
}

/*
function getNode(refs)
{
  var html = document.createElement("div");
  var authors = getActiveAuthors();
  if (authors.length == 0)
    return null;
  var authorsNodes = [];
  for(var i=0; i < authors.length; ++i)
  {
    var node = document.createElement("span");
    node.innerHTML = authors[i].name;
    authorsNodes.push(node);
  }

  for(var i=0; i < refs.length; ++i)
  {
    var aref = refs[i];
    var cindices = aref.getChapterIndices();
    for(var j=0; j < cindices.length; ++j)
    {
      var cidx = cindices[j];
      var vindices = aref.getVerseIndices(cidx);
      for(var k=0; k < vindices.length; ++k)
      {
        var vidx = vindices[k];
        var node = document.createElement("p");
        node.innerHTML = (cidx+1) + ":" + (vidx+1);
        html.appendChild(node);
        node = document.createElement("div");
        html.appendChild(node);
        for(var l=0; l < authors.length; ++l)
        {
          node.appendChild(authorsNodes[l].cloneNode(true));
          var verse = document.createElement("blockquote");
          verse.innerHTML = "<p>"+authors[l].chapters[cidx][vidx]+"</p>";
          node.appendChild(verse);
        }
      }
    }
  }
  return html;
}
*/

function selectChapter(select)
{
  show(select.value);
}

function getRandomReferences(num)
{
  if (num <= 0)
    return [];
  var refs = [];
  do
  {
    var cidx = Math.floor(Math.random()*100) % 114;
    var vidx = Math.floor(Math.random()*100) % verses_table[cidx];
    refs.push( new Reference([new Range(Type.Number, cidx+1)], [new Range(Type.Number, vidx+1)]) );
  } while(--num)
  return refs;
}

/**
  Parses a reference list and returns an array of Reference objects.
  Returns an empty array and shows an error message
  if an exception was thrown.
*/
function parseReferencesHE(str)
{
  var m;
  if (m = /^rand(om)? *(\d+)?$/.exec(str))
    return getRandomReferences(m.length == 3 ? parseInt(m[2]) : 1);

  var parser = new ReferenceListParser(str);
//   var tokens;
  var refs = [];
  try
  {
//     tokens = parser.getTokens();
    refs = parser.parseReferences();
  }
  catch (e)
  {
    if (!(e instanceof ParseError))
      throw e;
    var errorMsg = "";
    if (e.pos == str.length)
      errorMsg = str + '<em> </em>';
    else
      errorMsg = str.slice(0, e.pos) + "<em>" + str.charAt(e.pos) + "</em>" + str.slice(e.pos+1);
    errorMsg = "<pre>"+errorMsg+"</pre>"+"Error in reference list: " + e.msg;

    var errDiv = document.getElementById("error");
    errDiv.innerHTML = errorMsg;
    setTimeout("removeErrorMsg()", 6000);
  }
//   alert(tokens);
  return refs;
}

/**
  Parses a query string and returns a new Search object.
  Returns null and shows an error message
  if an exception was thrown.
*/
function parseQueryHE(q, matchany, highlight, casei)
{
  var search = null;
  try
  {
    search = new Search(q, matchany, highlight, casei);
  }
  catch(e)
  {
    var errDiv = document.getElementById("error");
    errDiv.innerHTML = "Error in query: " + e.message;
    setTimeout("removeErrorMsg()", 6000);
  }

  return search;
}

function removeErrorMsg()
{
  var errDiv = document.getElementById("error");
  errDiv.innerHTML = "";
}

function loadVerses(checkbox)
{
  var authors = getActiveAuthors();

  if (!authors.length)
    disableControls(true);
  else if (authors.length == 1) {
    disableControls(false);
    disableControls(true, ["interleave"]);
  }
  else if (authors.length > 1) {
    disableControls(false, ["interleave"]);
  }

  if (checkbox.isLoaded)
    return; // Author is already loaded

  var div = document.getElementById("verses");

  // Get the comment node with the verses of the requested author.
  var verses = div.childNodes[checkbox.authorIdx];

  // Verses are separated by '\n'. Splitting the contents of the
  // pre element will return an array of 6236 strings.
  var versesArray = getText(verses).split('\n');

  // Once the data is loaded, we can empty the pre element.
  verses.innerHTML = "";

  // Finally set the authors verses.
  g_Authors[checkbox.authorIdx].setVerses( versesArray );

  checkbox.isLoaded = true;
}

/**
  Enable or disable user controls.
*/
function disableControls(disabled, ids)
{
  if (ids == undefined || !(ids instanceof Array))
    ids = ["chapterList","refs","btnShow","interleave","search","btnSearch","matchany","casei","highlight", "restrict"];
  for(var i=0; i < ids.length; ++i)
  {
    document.getElementById(ids[i]).disabled = disabled;
  }
}

function getInnerText(node)
{
  return node.innerText;
}

function getTextContent(node)
{
  return node.textContent;
}

// A delegate to getInnerText or getTextContent.
var getText = getInnerText;

function init()
{
  disableControls(true);

  if (document.body.textContent)
    getText = getTextContent;

  // onkeydown event handler for text inputs.
  function onKeyDown(e)
  {
    if(!e) e = window.event;
    if (e.keyCode == 13)
    {
      if (this.id == "refs")
        show(this.value);
      else
        search(this.value);
      this.history.add(this.value);
    }
    else if(e.keyCode == 38)
      this.value = this.history.prev();
    else if(e.keyCode == 40)
      this.value = this.history.next();
  }
  // Prevents Opera from firing the default button,
  // which would do a search or a reference view twice.
  function onKeyPress(e) {
    if(!e) e = window.event;
    if(e.keyCode == 13)
      return false;
  }
  // Set event handler and new History instance for "refs" and "search".
  for (var i=0; i < 2; ++i)
  {
    var input = document.getElementById(["refs","search"][i]);
    input.history = new History();
    input.onkeydown = onKeyDown;
    input.onkeypress = onKeyPress;
  }

  // Set authors list
  var list = document.getElementById("authorList");

  for (var i=0; i < g_Authors.length; ++i)
  {
    var p = list.appendChild(document.createElement("p"));
    p.innerHTML = '<input onchange="loadVerses(this)" type="checkbox" id="author'+i+'"><span onclick="populateChapterList('+i+')">' + g_Authors[i].name + "</span></input>";
    // Add properties to input.
    var input = p.firstChild;
    input.isLoaded = false;
    input.authorIdx = i;
  }

  // Initialize chapter list.
  var chapterList = document.getElementById("chapterList");
  var option;
  for (var i=0; i < NR_OF_CHAPTERS; ++i)
  {
    option = chapterList.appendChild(document.createElement("option"));
    option.value = i+1;
    option.appendChild(document.createTextNode(""));
  }
  chapterList.authorIdx = -1;
  populateChapterList(0);
}

/// Empties the contents of a node and returns it.
/*
function empty(node)
{
  while(node.firstChild)
    node.removeChild( node.firstChild );
  return node
}
*/

function populateChapterList(authorIdx)
{
  var list = document.getElementById("chapterList");
  if (list.authorIdx == authorIdx)
    return;
  list.authorIdx = authorIdx;
//   list.className = g_Authors[authorIdx].langClass;

  var titles = g_Authors[authorIdx].titles;
  for (var i=0; i < titles.length; ++i)
    list.childNodes[i].firstChild.data = (i+1)+". "+titles[i];

  list.style.width = "auto"; // Required by IE
}

function showHelp()
{
  document.getElementById("help").className = "";
}

function closeHelp()
{
  document.getElementById("help").className = "hidden";
}

/*
function visibilityOfChapters(value)
{
  var span_collapse = document.getElementById("collapse");
  var span_expand = document.getElementById("expand");
  if (value == "hidden")
  {
    span_collapse.className = "hidden";
    span_expand.className = "";
  }
  else
  {
    span_expand.className = "hidden";
    span_collapse.className = "";
  }

  var divs = document.getElementsByTagName("div");
  for (var i = 0; i < divs.length; i++)
  {
    divs[i].className = value;
  }
}
*/
</script>
</head>
<body onload="init()" style="margin:0;padding:0;">
<h1><a href="http://code.google.com/p/openquran/">openquran</a> dhtml<br><span>Version 1.00-rc1</span></h1>
<p id="helplnk"><a href="javascript:showHelp()">Help</a></p>
<div style="margin:0px;padding:5px;">
<table cellpadding="5" valign="top">
<tr style="vertical-align:top;">
<td class="cellborder">
  References:<br/>
  <input type="text" id="refs" /> <button id="btnShow" onclick="show(document.getElementById('refs').value)">Show</button><br/>
  <input type="checkbox" id="interleave">interleave verses</input>
</td>
<td style="white-space:nowrap;" rowspan="2">
  Authors:<br/>
  <div id="authorList"></div>
</td>
<td rowspan="2">
  <select id="chapterList" multiple="true" size="12" onchange="selectChapter(this)"></select>
</td>
</tr>
<tr>
<td class="cellborder">
  Search:<br/>
  <input type="text" id="search" /> <button id="btnSearch" onclick="search(document.getElementById('search').value)">Search</button><br/>
  <input type="checkbox" id="matchany">match any</input><br/>
  <input type="checkbox" id="casei">case insensitive</input><br/>
  <input type="checkbox" id="highlight">highlight matches</input><br/>
  <input type="checkbox" id="restrict">restrict to references</input>
</td>
</tr>
</table>
<div id="error" onclick="removeErrorMsg()"></div>
<div id="help" class="hidden">
<a href="javascript:closeHelp()">Close Help</a>
<h2>1. Overview</h2>
<div>
<p>Enable an author for searching/browsing by clicking on his/her checkbox.
You can click on the label of an author to change the chapter list to the chapter names of the author.</p>
<p>Browse the Qur'an by clicking on the items in the chapter list or by entering references in the respective text box.</p>
<ul>
<li><em>interleave verses</em>: turn this option on if you want to compare verses.</li>
</ul>
<p>Enter some words in the search box to perform a query:</p>
<ul>
<li><em>match any</em>: matches any words given in the query. The default is matching all words.</li>
<li><em>case insensitive</em>: disregards the casing of the letters.</li>
<li><em>highlight matches</em>: highlights the words from the query in the text.</li>
<li><em>restrict to references</em>: search only in the references specified in the box above.</li>
</ul>
Search operators:
<ul>
<li>-: prepend a term with a minus to find verses that don't contain this term.</li>
<li>"...": put quotation marks around two or more words to search for them as a phrase.</li>
<li>/.../i: a forward slash starts a JavaScript regular expression and a second one terminates it. The "i" flag is optional and means case insensitive pattern matching. Regular expressions are a complicated and vast subject so I can't explain them here. Please, refer to <a href="http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:RegExp">Mozilla's RegExp page</a> for further information.</li>
</ul>
</div>
<h2>2. References</h2>
<div>
<p>A reference is composed of a part of chapter numbers and a part of verse numbers.
Both parts are joined by a colon (CP:VP), though VP can be left out to mean "all verses of that chapter."
In both parts you can specify a list of numbers and ranges separated by a comma.
Separate multiple references with a semicolon or a space. E.g.:</p>
<pre>
  22 49 58           # All verses of chapter 22, 49 and 58.
  1:3 2:286          # Verse 3 of chapter 1 and verse 286 of chapter 2.
  1,8:19,2,9,5,7     # Verses 19,2,9,5,7 of chapter 1 and 8.
  38-98,100:5-10,18  # Verses 5 to 10 and 18 of chapters 38 to 98 and 100.
  2-10:4-*           # Chapters 2 to 10, all verses from 4 to the end of each chapter.
  *:1,2              # First two verses of all chapters (equiv. to 1-114:1,2).
  24+3:34+6          # Relative ranges. Equivalent to 24-27:34-40
  3:7,187+10         # Verse 7 and verses 187 to 197 of chapter 3.
</pre>
<p style="font-size:0.8em;text-align:center;">Copyright © 2007 by Aziz Köksal<br/><a href="http://www.gnu.org/licenses/gpl2.html">Licensed under the GPL2</a></p>
</div>
</div>
<div id="debug" onclick="this.innerHTML=''">
</div>
<div id="text"></div>
</div>
<div id="verses" style="display:none">{%Verses%}</div>
</body>
</html>